﻿using System;
using System.Collections.Generic;
using System.Drawing;

namespace ERModelData
{
    public class MarkerLink
    {
        /// <summary>Объект визуализации</summary>
        private Rectangle visuality;
        /// <summary>Точка которая будет учавствовть в отрисовке связей</summary>
        public Point point;
        /// <summary>Список связей привязанных к этому маркеру</summary>
        public List<Link> arrayLinks;
        /// <summary>Конструктор маркера</summary>
        /// <param name="xCenter">Горизонтальная позиция центра</param>
        /// <param name="yCenter">Вертикальная позияция центра</param>
        public MarkerLink() { arrayLinks = new List<Link>(); }
        public MarkerLink(int xCenter, int yCenter) { Refresh(new Point(xCenter, yCenter)); arrayLinks = new List<Link>(); }
        /// <summary>Обновление расположение маркера</summary>
        /// <param name="newCenter">новые координаты центра</param>
        public void Refresh(Point newCenter)
        {
            point = newCenter;
            visuality = new Rectangle(
                newCenter.X - Config.cMarkerLink.size,
                newCenter.Y - Config.cMarkerLink.size,
                Config.cMarkerLink.size * 2,
                Config.cMarkerLink.size * 2
                );
        }
        /// <summary>Отрисовка маркера на указанную поверхность</summary>
        /// <param name="g">Поверхность отрисовки</param>
        public void Draw(Graphics g)
        {
            g.DrawRectangle(Config.cMarkerLink.pen, visuality);
            g.FillRectangle(Config.cMarkerLink.brush, visuality);
        }
        /// <summary>Отрисовка выделенного маркера на указанную поверхность</summary>
        /// <param name="g">Поверхность отрисовки</param>
        public void DrawSelect(Graphics g)
        {
            g.DrawRectangle(Config.cMarkerLink.penSelect, visuality);
            g.FillRectangle(Config.cMarkerLink.brushSelect, visuality);
        }
        /// <summary>Определение попадания точкив маркер</summary>
        /// <param name="position">Позиция точки</param>
        /// <returns>Флаг попадения</returns>
        public bool Contains(Point position)
        {
            return visuality.Contains(position);
        }
    }
    /// <summary>Реализация общего массива маркеров</summary>
    public class MarkersLink
    {
        /// <summary>Массив маркеров</summary>
        public MarkerLink[] arrayMarkers;
        private MarkerLink SelectMarker;
        /// <summary>Конструктор Маркера сущности</summary>
        /// <param name="ObjectVisuality">Визуальный объект сущности</param>
        public MarkersLink(EssenceVisuality ObjectVisuality)
        {
            arrayMarkers = new MarkerLink[4];
            for (int i = 0; i < 4; i++) arrayMarkers[i] = new MarkerLink();
            Refresh(GetPoints(ObjectVisuality.essenceObject));
        }
        /// <summary>Отрисовка всех маркеров в массиве на указанную поверхность</summary>
        /// <param name="g">поверхность для отрисовки</param>
        public void Draw(Graphics g)
        {
            foreach (MarkerLink i in arrayMarkers) i.Draw(g);
            if(SelectMarker != null)SelectMarker.DrawSelect(g);
        }
        /// <summary>Проверка попадания в маркер</summary>
        /// <param name="position">Позиция курсора</param>
        /// <returns>Ключ попадения</returns>
        public MarkerLink Check(Point position)
        {
            SelectMarker = null;
            foreach (MarkerLink i in arrayMarkers) if (i.Contains(position)) SelectMarker = i;
            return SelectMarker;
        }
        /// <summary>Обновление позиций маркеров</summary>
        /// <param name="newVisual">Новое положение объекта визуализации</param>
        public void Refresh(Point[] points)
        {
            int c = 0;
            foreach (MarkerLink i in arrayMarkers) i.Refresh(points[c++]);
        }
        /// <summary>Определяет точки центров маркеров сущности</summary>
        /// <param name="rect">Визуальный объект сущности</param>
        /// <returns>Массив точек центров</returns>
        public Point[] GetPoints(Rectangle rect)
        {
            List<Point> l = new List<Point>();
            l.Add(new Point(rect.Left + rect.Size.Width / 2, rect.Top));
            l.Add(new Point(rect.Left + rect.Size.Width / 2, rect.Bottom));
            l.Add(new Point(rect.Left, rect.Top + rect.Size.Height / 2));
            l.Add(new Point(rect.Right, rect.Top + rect.Size.Height / 2));
            return l.ToArray();
        }
    }
}
